#include "log.h"
#include "head.h"
#include "config.h"

#define PATH_LEVEL_DEBUG    "./log/LogDebug.log"
#define PATH_LEVEL_INFO     "./log/LogInfo.log"
#define PATH_LEVEL_WARNING  "./log/LogWarning.log"
#define PATH_LEVEL_ERROR    "./log/LogError.log"

#define LOG_VALUE_SIZE 128
#define LOG_BUF_SIZE 1024

// __LINE__         当前源代码行号
// __FUNCTION__     当前函数名称的字符串
// __FILE__         源文件名的字符串

/*定义全局变量g_log_level为LEVEL_INFO等级*/
Level g_log_level = LEVEL_INFO;


/*获取当前日期时间字符串*/
static int getDateTime(char *date_time);

/*拼接日志信息*/
static int getLogInfo(char *buf);



/*把日志等级由字符串转换为LeveL类型*/
int logStrToLevel(const char *str_level, Level *ptr_level){
    if(strncmp(str_level, STR_LEVEL_DEBUG, strlen(STR_LEVEL_DEBUG)) == 0){
        /*LEVEL_DEBUG*/
        *ptr_level = LEVEL_DEBUG;
        return 0;
    }
    if(strncmp(str_level, STR_LEVEL_INFO, strlen(STR_LEVEL_INFO)) == 0){
        /*LEVEL_INFO*/
        *ptr_level = LEVEL_INFO;
        return 0;
    }
    if(strncmp(str_level, STR_LEVEL_WARNING, strlen(STR_LEVEL_WARNING)) == 0){
        /*LEVEL_WARNING*/
        *ptr_level = LEVEL_WARNING;
        return 0;
    }
    if(strncmp(str_level, STR_LEVEL_ERROR, strlen(STR_LEVEL_ERROR)) == 0){
        /*LEVEL_ERROR*/
        *ptr_level = LEVEL_ERROR;
        return 0;
    }

    return -1;
}

/*把日志等级由LeveL转换为字符串类型*/
int logLevelToStr(Level level, char *str_level){
    if(level == LEVEL_DEBUG){
        /*LEVEL_DEBUG*/
        strcpy(str_level, STR_LEVEL_DEBUG);
        return 0;
    }
    if(level == LEVEL_INFO){
        /*LEVEL_INFO*/
        strcpy(str_level, STR_LEVEL_INFO);
        return 0;
    }
    if(level == LEVEL_WARNING){
        /*LEVEL_WARNING*/
        strcpy(str_level, STR_LEVEL_WARNING);
        return 0;
    }
    if(level == LEVEL_ERROR){
        /*LEVEL_ERROR*/
        strcpy(str_level, STR_LEVEL_ERROR);
        return 0;
    }
    return -1;
}



/*功能：获取配置文件中的日志等级，并设置,若配置文件中没有，则写入配置文件 默认等级LEVEL_FINO*/
int logGetLevel(Level *ptr_level){
    const char *key = KEY_LEVEL;
    char value[LOG_VALUE_SIZE] = {0};
    int ret = getParameter(KEY_LEVEL, value);

    if (ret == -1){
        /*配置文件没有日志等级*/
        setParameter(key,STR_LEVEL_INFO); 
    }else{
        /*配置文件有日志等级*/
        logStrToLevel(value, ptr_level);
        return 0;
    }
    return -1;
}

/*功能：更改需要打印的日志等级*/
int logSetLevel(Level level){
    /*设置全局变量*/
    g_log_level = level;

    /*设置配置文件*/
    const char *key = KEY_LEVEL;
    char value[LOG_VALUE_SIZE] = {0};
    logLevelToStr(level, value);
    setParameter(key, value);

    return 0;
}


/*功能：打印DEBUG信息*/
int logDebug(const char *msg){
    /*判断打印级别*/
    if(g_log_level > LEVEL_DEBUG){
        /*设置打印级别高于当前级别*/
        return 0;
    };

    /*打印*/
    FILE *fp = fopen(PATH_LEVEL_DEBUG, "a+");
    if(fp == NULL){
        return -1;
    }
    
    char log_info[LOG_BUF_SIZE] = {0};
    getLogInfo(log_info);
    
    char buf[LOG_BUF_SIZE << 1] = {0};
    sprintf(buf, "Debug：%s\t %s\n", log_info, msg);

    int ret = fwrite(buf, sizeof(char), strlen(buf), fp);
    if(ret == -1){
        return -1;
    }

    fclose(fp);
    return 0;
}

/*功能：打印普通信息*/
int logInfo(const char *msg){
    /*判断打印级别*/
    if(g_log_level > LEVEL_INFO){
        /*设置打印级别高于当前级别*/
        return 0;
    };

    /*打印*/
    FILE *fp = fopen(PATH_LEVEL_INFO, "a+");
    if(fp == NULL){
        return -1;
    }
    
    char log_info[LOG_BUF_SIZE] = {0};
    getLogInfo(log_info);
    
    char buf[LOG_BUF_SIZE << 1] = {0};
    sprintf(buf, "Info：%s\t %s\n", log_info, msg);

    int ret = fwrite(buf, sizeof(char), strlen(buf), fp);
    if(ret == -1){
        return -1;
    }

    fclose(fp);
    return 0;
}

/*功能：打印警告信息*/
int logWarning(const char *msg){
    /*判断打印级别*/                  
    if(g_log_level > LEVEL_WARNING){     
        /*设置打印级别高于当前级别*/  
        return 0;                     
    };

    /*打印*/
    FILE *fp = fopen(PATH_LEVEL_WARNING, "a+");
    if(fp == NULL){
        return -1;
    }
    
    char log_info[LOG_BUF_SIZE] = {0};
    getLogInfo(log_info);
    
    char buf[LOG_BUF_SIZE << 1] = {0};
    sprintf(buf, "WARNING：%s\t %s\n", log_info, msg);

    int ret = fwrite(buf, sizeof(char), strlen(buf), fp);
    if(ret == -1){
        return -1;
    }

    fclose(fp);
    return 0;
}

/*功能：打印错误信息*/
int logError(const char *msg){
    /*判断打印级别*/                  
    if(g_log_level > LEVEL_ERROR){     
        /*设置打印级别高于当前级别*/  
        return 0;                     
    };     

    /*打印*/
    FILE *fp = fopen(PATH_LEVEL_ERROR, "a+");
    if(fp == NULL){
        return -1;
    }
    
    char log_info[LOG_BUF_SIZE] = {0};
    getLogInfo(log_info);
    
    char buf[LOG_BUF_SIZE << 1] = {0};
    sprintf(buf, "ERROR：%s\t %s\n", log_info, msg);

    int ret = fwrite(buf, sizeof(char), strlen(buf), fp);
    if(ret == -1){
        return -1;
    }

    fclose(fp);
    return 0;
}




/*获取当前日期时间字符串*/
static int getDateTime(char *date_time){
    time_t t;
    struct tm *ptr_timeInfo;

    time(&t);
    ptr_timeInfo = localtime(&t);

    strftime(date_time, 80, "%Y-%m-%d %H:%M:%S", ptr_timeInfo);

    return 0;
}


/*拼接日志信息*/
static int getLogInfo(char *buf){
    char date_time[LOG_BUF_SIZE] = {0};
    getDateTime(date_time);
    
    sprintf(
            buf, "%s\t 文件名：%s\t 函数名%s\t 行数%d",
            date_time, __FILE__, __FUNCTION__, __LINE__
           );

    return 0;
}

/**/
